using System;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Media;

namespace PropertyExpression.PresentationCode
{
    public static class CollectionPropertyExtensions
    {
        public static T Add<T, TCollection, TElement>(
            this T arg,
            Func<T, TCollection> propertyExpression,
            Action<TCollection, TElement> action,
            params TElement[] values)
        {
            var collection = propertyExpression(arg);
            foreach (var value in values)
            {
                action(collection, value);
            }
            return arg;
        }
    }

    public static class ColumnDefinitionCollectionPropertyExtensions
    {
        public static T Add<T>(
            this T arg,
            Func<T, ColumnDefinitionCollection> propertyExpression,
            params ColumnDefinition[] values)
        {
            return arg.Add(propertyExpression,
                         (collection, element) => collection.Add(element),
                         values);
        }
    }

    public static class UIElementCollectionPropertyExtensions
    {
        public static T Add<T>(
            this T arg,
            Func<T, UIElementCollection> propertyExpression,
            params UIElement[] values)
        {
            return arg.Add(propertyExpression,
                         (collection, element) => collection.Add(element),
                         values);
        }
    }

    public static class RowDefinitionCollectionPropertyExtensions
    {
        public static T Add<T>(
            this T arg,
            Func<T, RowDefinitionCollection> propertyExpression,
            params RowDefinition[] values)
        {
            return arg.Add(propertyExpression,
                         (collection, element) => collection.Add(element),
                         values);
        }
    }

    public static class SetterBaseCollectionPropertyExtensions
    {
        public static T Add<T>(
            this T arg,
            Func<T, SetterBaseCollection> propertyExpression,
            params SetterBase[] values)
        {
            return arg.Add(propertyExpression,
                         (collection, element) => collection.Add(element),
                         values);
        }
    }

    public static class TriggerBaseCollectionPropertyExtensions
    {
        public static T Add<T>(
            this T arg,
            Func<T, TriggerCollection> propertyExpression,
            params TriggerBase[] values)
        {
            return arg.Add(propertyExpression,
                         (collection, element) => collection.Add(element),
                         values);
        }
    }

    public static class GradientStopCollectionPropertyExtensions
    {
        public static T Add<T>(
            this T arg,
            Func<T, GradientStopCollection> propertyExpression,
            params GradientStop[] values)
        {
            return arg.Add(propertyExpression,
                         (collection, element) => collection.Add(element),
                         values);
        }
    }
}